<?php

class SiteController extends Controller
{
	/**
	 * Declares class-based actions.
	 */
	public function actions()
	{
		return array(
			// captcha action renders the CAPTCHA image displayed on the contact page
			'captcha'=>array(
				'class'=>'CCaptchaAction',
				'backColor'=>0xFFFFFF,
			),
			// page action renders "static" pages stored under 'protected/views/site/pages'
			// They can be accessed via: index.php?r=site/page&view=FileName
			'page'=>array(
				'class'=>'CViewAction',
			),
		);
	}

	/**
	 * This is the default 'index' action that is invoked
	 * when an action is not explicitly requested by users.
	 */
	public function actionIndex()
	{
		// renders the view file 'protected/views/site/index.php'
		// using the default layout 'protected/views/layouts/main.php'
        $model=Book::model()->findAll($params=array('order'=>'vote DESC','limit'=>4));
        $modelBrowsertimes=Book::model()->findAll($params=array('order'=>'browsertimes DESC','limit'=>4));
        $this->render('index',array(
            'model'=>$model,
            'modelBrowsertimes'=>$modelBrowsertimes,
        ));
	}

	/**
	 * This is the action to handle external exceptions.
	 */
	public function actionError()
	{
		if($error=Yii::app()->errorHandler->error)
		{
			if(Yii::app()->request->isAjaxRequest)
				echo $error['message'];
			else
				$this->render('error', $error);
		}
	}

	/**
	 * Displays the contact page
	 */
	public function actionContact()
	{
		$model=new ContactForm;
		if(isset($_POST['ContactForm']))
		{
			$model->attributes=$_POST['ContactForm'];
			if($model->validate())
			{
                $mail = Yii::createComponent('application.extensions.mailer.EMailer');
                $message = 'Hello World!';
                $mail->Host = 'smtp.163.com';
                $mail->Port = 25;
                $mail->IsSMTP();
                $mail->SMTPAuth= true;
                $mail->Username = "yp2800@163.com";//你的用户名，或者完整邮箱地址
                $mail->Password = "xxxxxxxxxxxxxx";//邮箱密码
                $mail->AddAddress('360929805@qq.com');

				$name=$model->name;
                $mail->SetFrom('yp2800@163.com', $name);//发送的邮箱和发送人
				$subject=$model->subject;
                $mail->Subject = $subject;
				// $headers="From: $name <{$model->email}>\r\n".
					// "Reply-To: {$model->email}\r\n".
					// "MIME-Version: 1.0\r\n".
					// "Content-Type: text/plain; charset=UTF-8";

				// mail(Yii::app()->params['adminEmail'],$subject,$model->body,$headers);
                $mail->Body = $model->body;
                echo $mail->Send();
				// Yii::app()->use:->setFlash('contact','非常感谢您提供的宝贵意见.');
				$this->refresh();
			}
		}
		$this->render('contact',array('model'=>$model));
	}

	/**
	 * Displays the login page
	 */
	public function actionLogin()
	{
		$model=new LoginForm;

		// if it is ajax validation request
		if(isset($_POST['ajax']) && $_POST['ajax']==='login-form')
		{
			echo CActiveForm::validate($model);
			Yii::app()->end();
		}

		// collect user input data
		if(isset($_POST['LoginForm']))
		{
			$model->attributes=$_POST['LoginForm'];
			// validate user input and redirect to the previous page if valid
			if($model->validate() && $model->login())
				$this->redirect(Yii::app()->user->returnUrl);
		}
		// display the login form
		$this->render('login',array('model'=>$model));
	}

	/**
	 * Logs out the current user and redirect to homepage.
	 */
	public function actionLogout()
	{
		Yii::app()->user->logout();
		$this->redirect(Yii::app()->homeUrl);
	}

	/**
	 * register
	 */
	public function actionRegister()
	{
        $user=new User;
        if(isset($_POST['User'])){
            $user->attributes=$_POST['User'];
            if($user->save()){
                Yii::app()->user->setFlash('success','注册成功请登陆');
                $this->redirect(array('/site/login','message'=>'注册成功，跳转登陆界面'));
            }else{
                echo 'error';
            }
        }
        $this->render("register",array("model"=>$user));
	}
	/**
	 * 聊天
	 */
	public function actionChat(){
        $this->render("chat",array("model"=>'yp2800'));
    }
	/**
	 * 聊天
	 */
	public function actionChatHandler()
	{
        $host = 'localhost'; //host
        $port = '9000'; //port
        $null = NULL; //null var

        //Create TCP/IP sream socket
        $socket = socket_create(AF_INET, SOCK_STREAM, SOL_TCP);
        //reuseable port
        socket_set_option($socket, SOL_SOCKET, SO_REUSEADDR, 1);

        //bind socket to specified host
        socket_bind($socket, 0, $port);

        //listen to port
        socket_listen($socket);

        //create & add listning socket to the list
        $clients = array($socket);

        //start endless loop, so that our script doesn't stop
        while (true) {
        	//manage multipal connections
        	$changed = $clients;
        	//returns the socket resources in $changed array
        	socket_select($changed, $null, $null, 0, 10);

        	//check for new socket
        	if (in_array($socket, $changed)) {
        		$socket_new = socket_accept($socket); //accpet new socket
        		$clients[] = $socket_new; //add socket to client array

        		$header = socket_read($socket_new, 1024); //read data sent by the socket
        		perform_handshaking($header, $socket_new, $host, $port); //perform websocket handshake

        		socket_getpeername($socket_new, $ip); //get ip address of connected socket
        		$response = mask(json_encode(array('type'=>'system', 'message'=>$ip.' connected'))); //prepare json data
        		send_message($response); //notify all users about new connection

        		//make room for new socket
        		$found_socket = array_search($socket, $changed);
        		unset($changed[$found_socket]);
        	}

        	//loop through all connected sockets
        	foreach ($changed as $changed_socket) {

        		//check for any incomming data
        		while(socket_recv($changed_socket, $buf, 1024, 0) >= 1)
        		{
        			$received_text = unmask($buf); //unmask data
        			$tst_msg = json_decode($received_text); //json decode
        			$user_name = $tst_msg->name; //sender name
        			$user_message = $tst_msg->message; //message text
        			$user_color = $tst_msg->color; //color

        			//prepare data to be sent to client
        			$response_text = mask(json_encode(array('type'=>'usermsg', 'name'=>$user_name, 'message'=>$user_message, 'color'=>$user_color)));
        			send_message($response_text); //send data
        			break 2; //exist this loop
        		}

        		$buf = @socket_read($changed_socket, 1024, PHP_NORMAL_READ);
        		if ($buf === false) { // check disconnected client
        			// remove client for $clients array
        			$found_socket = array_search($changed_socket, $clients);
        			socket_getpeername($changed_socket, $ip);
        			unset($clients[$found_socket]);

        			//notify all users about disconnected connection
        			$response = mask(json_encode(array('type'=>'system', 'message'=>$ip.' disconnected')));
        			send_message($response);
        		}
        	}
        }
        // close the listening socket
        socket_close($sock);
	}
    function send_message($msg)
    {
    	global $clients;
    	foreach($clients as $changed_socket)
    	{
    		@socket_write($changed_socket,$msg,strlen($msg));
    	}
    	return true;
    }


    //Unmask incoming framed message
    function unmask($text) {
    	$length = ord($text[1]) & 127;
    	if($length == 126) {
    		$masks = substr($text, 4, 4);
    		$data = substr($text, 8);
    	}
    	elseif($length == 127) {
    		$masks = substr($text, 10, 4);
    		$data = substr($text, 14);
    	}
    	else {
    		$masks = substr($text, 2, 4);
    		$data = substr($text, 6);
    	}
    	$text = "";
    	for ($i = 0; $i < strlen($data); ++$i) {
    		$text .= $data[$i] ^ $masks[$i%4];
    	}
    	return $text;
    }

    //Encode message for transfer to client.
    function mask($text)
    {
    	$b1 = 0x80 | (0x1 & 0x0f);
    	$length = strlen($text);

    	if($length <= 125)
    		$header = pack('CC', $b1, $length);
    	elseif($length > 125 && $length < 65536)
    		$header = pack('CCn', $b1, 126, $length);
    	elseif($length >= 65536)
    		$header = pack('CCNN', $b1, 127, $length);
    	return $header.$text;
    }

    //handshake new client.
    function perform_handshaking($receved_header,$client_conn, $host, $port)
    {
    	$headers = array();
    	$lines = preg_split("/\r\n/", $receved_header);
    	foreach($lines as $line)
    	{
    		$line = chop($line);
    		if(preg_match('/\A(\S+): (.*)\z/', $line, $matches))
    		{
    			$headers[$matches[1]] = $matches[2];
    		}
    	}

    	$secKey = $headers['Sec-WebSocket-Key'];
    	$secAccept = base64_encode(pack('H*', sha1($secKey . '258EAFA5-E914-47DA-95CA-C5AB0DC85B11')));
    	//hand shaking header
    	$upgrade  = "HTTP/1.1 101 Web Socket Protocol Handshake\r\n" .
    	"Upgrade: websocket\r\n" .
    	"Connection: Upgrade\r\n" .
    	"WebSocket-Origin: $host\r\n" .
    	"WebSocket-Location: ws://$host:$port/demo/shout.php\r\n".
    	"Sec-WebSocket-Accept:$secAccept\r\n\r\n";
    	socket_write($client_conn,$upgrade,strlen($upgrade));
    }
}
